const setValueByPath = require("./template.js")

function testSetValueByPath() {
  console.log(
    "1. 基本路径设置:",
    (() => {
      const obj = {}
      setValueByPath(obj, ["a"], "value1")
      return obj.a === "value1"
    })()
  )

  console.log(
    "2. 嵌套路径设置:",
    (() => {
      const obj = {}
      setValueByPath(obj, ["a", "b", "c"], "deep_value")
      return obj.a.b.c === "deep_value"
    })()
  )

  console.log(
    "3. 覆盖已存在的值:",
    (() => {
      const obj = { a: { b: "old_value" } }
      setValueByPath(obj, ["a", "b"], "new_value")
      return obj.a.b === "new_value"
    })()
  )

  console.log(
    "4. 部分路径存在:",
    (() => {
      const obj = { a: { existing: "keep" } }
      setValueByPath(obj, ["a", "b", "c"], "value")
      return obj.a.existing === "keep" && obj.a.b.c === "value"
    })()
  )

  console.log(
    "5. 数字作为路径:",
    (() => {
      const obj = {}
      setValueByPath(obj, ["items", "0", "name"], "first_item")
      return obj.items["0"].name === "first_item"
    })()
  )

  console.log(
    "6. 设置不同类型的值:",
    (() => {
      const obj = {}
      setValueByPath(obj, ["string"], "text")
      setValueByPath(obj, ["number"], 42)
      setValueByPath(obj, ["boolean"], true)
      setValueByPath(obj, ["null"], null)
      setValueByPath(obj, ["undefined"], undefined)

      return (
        obj.string === "text" &&
        obj.number === 42 &&
        obj.boolean === true &&
        obj.null === null &&
        obj.undefined === undefined
      )
    })()
  )

  console.log(
    "7. 设置对象和数组:",
    (() => {
      const obj = {}
      const objValue = { nested: "object" }
      const arrValue = [1, 2, 3]

      setValueByPath(obj, ["data", "object"], objValue)
      setValueByPath(obj, ["data", "array"], arrValue)

      return obj.data.object === objValue && obj.data.array === arrValue
    })()
  )

  console.log(
    "8. 长路径设置:",
    (() => {
      const obj = {}
      setValueByPath(
        obj,
        ["level1", "level2", "level3", "level4", "level5"],
        "deep"
      )
      return obj.level1.level2.level3.level4.level5 === "deep"
    })()
  )

  console.log(
    "9. 空路径数组:",
    (() => {
      const obj = { original: "value" }
      try {
        setValueByPath(obj, [], "new_value")
        // 空路径应该不会改变对象
        return obj.original === "value"
      } catch (e) {
        // 或者可能抛出错误，这也是合理的
        return true
      }
    })()
  )

  console.log(
    "10. 单个路径元素:",
    (() => {
      const obj = {}
      setValueByPath(obj, ["root"], { child: "value" })
      return obj.root.child === "value"
    })()
  )

  console.log(
    "11. 覆盖非对象属性:",
    (() => {
      const obj = { a: "string_value" }
      setValueByPath(obj, ["a", "b"], "new_value")
      // 原来的字符串会被对象覆盖
      return typeof obj.a === "object" && obj.a.b === "new_value"
    })()
  )

  console.log(
    "12. 多次设置同一路径:",
    (() => {
      const obj = {}
      setValueByPath(obj, ["path", "to", "value"], "first")
      setValueByPath(obj, ["path", "to", "value"], "second")
      setValueByPath(obj, ["path", "to", "value"], "third")
      return obj.path.to.value === "third"
    })()
  )

  console.log(
    "13. 设置后验证结构完整性:",
    (() => {
      const obj = {}
      setValueByPath(obj, ["a", "b"], "value1")
      setValueByPath(obj, ["a", "c"], "value2")
      setValueByPath(obj, ["d", "e"], "value3")

      return (
        obj.a.b === "value1" &&
        obj.a.c === "value2" &&
        obj.d.e === "value3" &&
        typeof obj.a === "object" &&
        typeof obj.d === "object"
      )
    })()
  )

  console.log(
    "14. 特殊字符作为路径:",
    (() => {
      const obj = {}
      setValueByPath(
        obj,
        ["key-with-dash", "key.with.dot", "key with space"],
        "special"
      )
      return (
        obj["key-with-dash"]["key.with.dot"]["key with space"] === "special"
      )
    })()
  )

  console.log(
    "15. 原对象引用保持:",
    (() => {
      const obj = { existing: "data" }
      const originalRef = obj
      setValueByPath(obj, ["new", "path"], "value")

      return (
        obj === originalRef &&
        obj.existing === "data" &&
        obj.new.path === "value"
      )
    })()
  )

  console.log(
    "16. this上下文测试:",
    (() => {
      const obj = {
        data: {},
        setValue: function(path, value) {
          return setValueByPath(this.data, path, value)
        }
      }
      obj.setValue(["test"], "value")
      return obj.data.test === "value"
    })()
  )

  console.log(
    "17. 方法调用this绑定:",
    (() => {
      const obj = {
        prefix: "config_",
        data: {},
        setConfig: function(key, value) {
          const path = [this.prefix + key]
          setValueByPath(this.data, path, value)
        }
      }
      obj.setConfig("theme", "dark")
      return obj.data.config_theme === "dark"
    })()
  )

  console.log(
    "18. 复杂对象this绑定:",
    (() => {
      const obj = {
        settings: {
          user: {},
          system: {}
        },
        setUserSetting: function(key, value) {
          setValueByPath(this.settings.user, [key], value)
        }
      }
      obj.setUserSetting("language", "zh-CN")
      return obj.settings.user.language === "zh-CN"
    })()
  )

  console.log(
    "19. 回调函数this绑定:",
    (() => {
      const obj = {
        namespace: "app",
        data: {},
        setNestedValue: function(path, value) {
          const fullPath = [this.namespace, ...path]
          setValueByPath(this.data, fullPath, value)
        }
      }
      obj.setNestedValue(["user", "name"], "Alice")
      return obj.data.app.user.name === "Alice"
    })()
  )
}

testSetValueByPath()
